package com.aps.util;

import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.math.BigDecimal;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.ArrayList;
import java.util.List;

import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.RowMapper;

import lombok.extern.slf4j.Slf4j;

/**
 * @author liaoguangan
 * @description <>
 * @date 2018/4/4 13:46
 */
@Slf4j
public class JdbcQueryUtil<T> {

    private Class<T> tCls;
    private T t;
    private List<T> ts = new ArrayList<T>();

    public JdbcQueryUtil(Class<T> tCls) {
        this.tCls = tCls;
    }

    public T query(JdbcTemplate jdbcTemplate, String sql, Object[] params) {
        jdbcTemplate.query(sql, params, new RowMapper<T>() {

            @Override
            public T mapRow(ResultSet rs, int rowNum) throws SQLException {
                return invoke(rs);
            }
        });

        return t;
    }

    public List<T> queryList(JdbcTemplate jdbcTemplate, String sql, Object[] params) {
        jdbcTemplate.query(sql, params, new RowMapper<T>() {

            @Override
            public T mapRow(ResultSet rs, int rowNum) throws SQLException {
                ts.add(invoke(rs));
                return t;
            }
        });

        return ts;
    }

    private T invoke(ResultSet rs) {
        try {
            t = (T) tCls.newInstance();
        } catch (Exception e) {
            e.printStackTrace();
        }
        List<Field> fdList = new ArrayList<Field>();
        Field[] fds = JdbcUtil.getAllFields(tCls, fdList);
        for (Field fd : fds) {
            try {
                if (JdbcUtil.hasColumn(rs, JdbcUtil.getDbFieldName(fd.getName()))) {
                    Method method = tCls.getMethod(JdbcUtil.getSetMethodByField(fd.getName()),
                            fd.getType());
                    if (null == rs.getObject(JdbcUtil.getDbFieldName(fd.getName()))) {
                        continue;
                    }
                    if (fd.getType().isEnum()) { //枚举类型
                        method.invoke(t, JdbcUtil.str2Enum(
                                rs.getObject(JdbcUtil.getDbFieldName(fd.getName())).toString(),
                                fd));
                    } else if (fd.getType() == BigDecimal.class) {
                        method.invoke(t, rs.getBigDecimal(JdbcUtil.getDbFieldName(fd.getName())));
                    } else {
                        method.invoke(t, rs.getObject(JdbcUtil.getDbFieldName(fd.getName())));
                    }

                } else {
                    log.info("没有找到字段" + fd.getName());
                }
            } catch (Exception e) {
                log.error("JdbcQueryUtil invoke error");
                e.printStackTrace();
            }
        }
        return t;
    }
}
